package com.sen.gulimall.order.config;

import com.sen.common.constant.OrderConstant;
import com.sen.common.constant.WareConstant;
import org.springframework.amqp.core.*;
import org.springframework.amqp.support.converter.Jackson2JsonMessageConverter;
import org.springframework.amqp.support.converter.MessageConverter;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

import java.util.HashMap;
import java.util.Map;

/**
 * @author Kisen
 * @email lqs0911@qq.com
 * @date 2022/11/18 11:38
 * @detail
 */
@Configuration
public class RabbitMQConfig {

    /**
     * 使用JSON序列化机制，进行消息转换
     *
     * @return
     */
    @Bean
    public MessageConverter messageConverter() {
        return new Jackson2JsonMessageConverter();
    }

    @Bean
    public DirectExchange helloDirectExchange() {
        return ExchangeBuilder.directExchange(OrderConstant.HELLO_DIRECT_EXCHANGE)
                .durable(true)
                .build();
    }

    @Bean
    public Queue helloDirectQueue() {
        return QueueBuilder.durable(OrderConstant.HELLO_DIRECT_QUEUE)
                .build();
    }

    @Bean
    public Binding helloDirectQueueBindingExchange(@Qualifier("helloDirectQueue") Queue helloDirectQueue,
                                                   @Qualifier("helloDirectExchange") DirectExchange helloDirectExchange) {
        return BindingBuilder.bind(helloDirectQueue).to(helloDirectExchange)
                .with(OrderConstant.HELLO_DIRECT_ROUTE_KEY);
    }


    /**
     * 定时关单交换机
     *
     * @return
     */
    @Bean
    public TopicExchange orderEventExchange() {
        return ExchangeBuilder.topicExchange(OrderConstant.ORDER_EVENT_EXCHANGE)
                .durable(true)
                .build();
    }

    /**
     * 定时关单延时队列
     *
     * @return
     */
    @Bean
    public Queue orderDelayQueue() {
        Map<String, Object> arguments = new HashMap<>(3);
        // 声明当前队列绑定的死信交换机
        arguments.put("x-dead-letter-exchange", OrderConstant.ORDER_EVENT_EXCHANGE);
        // 声明当前队列的死信路由 key
        arguments.put("x-dead-letter-routing-key", OrderConstant.ORDER_RELEASE_ORDER_ROUTING_KEY);
        // 声明队列的TTL
        arguments.put("x-message-ttl", 60000);
        return QueueBuilder.durable(OrderConstant.ORDER_DELAY_QUEUE)
                .withArguments(arguments)
                .build();
    }

    /**
     * 定时关单-订单释放队列
     *
     * @return
     */
    @Bean
    public Queue orderReleaseOrderQueue() {
        return QueueBuilder.durable(OrderConstant.ORDER_RELEASE_ORDER_QUEUE).build();
    }

    /**
     * 定时关单-下单绑定路由
     *
     * @param orderDelayQueue
     * @param orderEventExchange
     * @return
     */
    @Bean
    public Binding orderCreateOrderBinding(@Qualifier("orderDelayQueue") Queue orderDelayQueue,
                                           @Qualifier("orderEventExchange") TopicExchange orderEventExchange) {
        return BindingBuilder.bind(orderDelayQueue).to(orderEventExchange).with(OrderConstant.ORDER_CREATE_ORDER_ROUTING_KEY);
    }

    /**
     * 定时关单-订单释放绑定路由
     *
     * @param orderReleaseOrderQueue
     * @param orderEventExchange
     * @return
     */
    @Bean
    public Binding orderReleaseOrderBinding(@Qualifier("orderReleaseOrderQueue") Queue orderReleaseOrderQueue,
                                            @Qualifier("orderEventExchange") TopicExchange orderEventExchange) {
        return BindingBuilder.bind(orderReleaseOrderQueue).to(orderEventExchange).with(OrderConstant.ORDER_RELEASE_ORDER_ROUTING_KEY);
    }

    /**
     * 订单释放直接和库存释放进行绑定
     *
     * @return
     */
    @Bean
    public Binding orderReleaseOtherBinding() {
        return new Binding(WareConstant.STOCK_RELEASE_STOCK_QUEUE,
                Binding.DestinationType.QUEUE,
                OrderConstant.ORDER_EVENT_EXCHANGE,
                OrderConstant.ORDER_RELEASE_OTHER_ROUTING_KEY,
                null);
    }

    /**
     * 创建秒杀单队列
     *
     * @return
     */
    @Bean
    public Queue orderSeckillOrderQueue() {
        return QueueBuilder.durable(OrderConstant.ORDER_SECKILL_ORDER_QUEUE).build();
    }

    /**
     * 秒杀单队列绑定关系
     *
     * @param orderSeckillOrderQueue
     * @param orderEventExchange
     * @return
     */
    @Bean
    public Binding orderSeckillOrderBinding(@Qualifier("orderSeckillOrderQueue") Queue orderSeckillOrderQueue,
                                            @Qualifier("orderEventExchange") TopicExchange orderEventExchange) {
        return BindingBuilder.bind(orderSeckillOrderQueue).to(orderEventExchange).with(OrderConstant.ORDER_SECKILL_ORDER_ROUTING_KEY);
    }

}
